
namespace Patterns4Net.Core.AttributesPatterns
{
    using System.Diagnostics.Contracts;
    using System.Linq;
    using Mono.Cecil;
    using Attributes.DesignPatterns;
    using Patterns;
    using Attributes;

    [PatternCreatorExport(typeof(VisitorAttribute))]
    public class VisitorCreator : ICreatePatternFromAttribute
    {
        public IPattern Crate(CustomAttribute attribute, IMemberDefinition targetType)
        {
            Contract.Assume(attribute.HasConstructorArguments);
            Contract.Assume(attribute.ConstructorArguments.Count == 1);
            Contract.Assume(attribute.ConstructorArguments.First().Value is TypeReference);

            bool isReflective = false;
            if (attribute.Properties.Any())
            {
                Contract.Assume(attribute.Properties.Count() == 1);
                Contract.Assume(attribute.Properties.First().Argument.Value is bool);
                isReflective = (bool)attribute.Properties.First().Argument.Value;
            }

            return new Visitor(
                (TypeDefinition)targetType, 
                (TypeReference)attribute.ConstructorArguments.First().Value, 
                isReflective);
        }
    }
}
